/*
 * To change this template, choose Tools | Templates
 * and open the template in the editor.
 */

package controller;

import entity.Customer;
import java.io.IOException;
import java.util.ArrayList;
import java.util.StringTokenizer;
import java.util.regex.Matcher;
import java.util.regex.Pattern;
import javax.ejb.EJB;
import javax.servlet.ServletException;
import javax.servlet.http.HttpServlet;
import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;
import session.CustomerFacade;

/**
 *
 * @author Elise
 */
public class CustomerServlet extends HttpServlet {
    @EJB
    private CustomerFacade customerFacade;

    // <editor-fold defaultstate="collapsed" desc="HttpServlet methods. Click on the + sign on the left to edit the code.">
    /** 
     * Handles the HTTP <code>GET</code> method.
     * @param request servlet request
     * @param response servlet response
     * @throws ServletException if a servlet-specific error occurs
     * @throws IOException if an I/O error occurs
     */
    @Override
    protected void doGet(HttpServletRequest request, HttpServletResponse response)
    throws ServletException, IOException {
                // Process request (Perform actions, set response attributes, set path for forward dispatch)

        String pathInfo = request.getPathInfo();
        pathInfo = (pathInfo == null) ? "" : pathInfo;

        //View for forward dispatch.
        String fdPath = null;

        Pattern p = Pattern.compile("/(\\d+)(/(\\w+))?"); // matches to /id/action
        Matcher m = p.matcher(pathInfo);
        m.find();
        Long customerId;
        String action;
        try {
            customerId = Long.parseLong(m.group(1));
        } catch (Exception nfe) {
            customerId = null;
        }
        try{
            action = m.group(3);
        }catch (Exception ex) {
            action = null;
        }

        ////////////////////////////////////////////////////////////////////////
        //CREATE
        if(pathInfo.equals("/new")) {
            fdPath = "/WEB-INF/view/customers/addCustomer.jsp";
        }
        ////////////////////////////////////////////////////////////////////////
        //READ
        else if (pathInfo.equals("")) {
            request.setAttribute("customers", customerFacade.findAll());
            fdPath = "/WEB-INF/view/customers/default.jsp";
        }
        ////////////////////////////////////////////////////////////////////////
        else if(pathInfo.equals("/search")) {
            //Request process of search.
            StringTokenizer st = new StringTokenizer(request.getParameter("searchTerm"));
            ArrayList returned = new ArrayList();
            try{
                //Search each search term component
                while(st.hasMoreElements()){
                 returned.addAll(customerFacade.queryByName(st.nextToken()));
                }
                //Remove duplicates.
                ArrayList results = new ArrayList();
                for(Object item : returned){
                    if(!results.contains(item)) results.add(item);
                }
                request.setAttribute("customers", results);
            }
            catch(Exception ex){
                request.setAttribute("searchCustomerFailureFlag", true);
            }
            fdPath = "/WEB-INF/view/customers/searchResults.jsp";
        }
        ////////////////////////////////////////////////////////////////////////
        else if (customerId != null && action == null) {
            Customer customer = customerFacade.find(customerId);
            if(customer !=null){
                request.setAttribute("customer", customer);
                fdPath = "/WEB-INF/view/customers/viewCustomer.jsp";
            }
            else{
                request.setAttribute("faultyId", customerId);
                fdPath = "/WEB-INF/view/customers/noSuchCustomer.jsp";
            }
        }
        ////////////////////////////////////////////////////////////////////////
        // UPDATE
        else if (customerId != null && action.equals("edit") ) {
            Customer customer = customerFacade.find(customerId);
            if(customer != null) {
                request.setAttribute("customer", customer);
                fdPath = "/WEB-INF/view/customers/editCustomer.jsp";
            }
            else{
                request.setAttribute("faultyId", customerId);
                fdPath = "/WEB-INF/view/customers/noSuchCustomer.jsp";
            }
        }
        ////////////////////////////////////////////////////////////////////////
        // DELETE
        else if (customerId != null && action.equals("remove")) {
            Customer customer = customerFacade.find(customerId);
            if(customer != null){
                request.setAttribute("customer", customer);
                fdPath = "/WEB-INF/view/customers/deleteCustomer.jsp";
            }
            else{
                request.setAttribute("faultyId", customerId);
                fdPath = "/WEB-INF/view/customers/noSuchCustomer.jsp";
            }
        }
        ////////////////////////////////////////////////////////////////////////
        // Forward dispatch
        if(fdPath == null)
            fdPath = "/WEB-INF/jspf/error/404.jsp";

        request.getRequestDispatcher(fdPath).forward(request, response);
    }

    /** 
     * Handles the HTTP <code>POST</code> method.
     * @param request servlet request
     * @param response servlet response
     * @throws ServletException if a servlet-specific error occurs
     * @throws IOException if an I/O error occurs
     */
    @Override
    protected void doPost(HttpServletRequest request, HttpServletResponse response)
    throws ServletException, IOException {
        // Process request (Perform actions, set response attributes, set path for forward dispatch)
        String pathInfo = request.getPathInfo();
        pathInfo = (pathInfo == null) ? "" : pathInfo;
        String fdPath = null;
        Pattern p = Pattern.compile("/(\\d+)(/(\\w+))?"); // matches to /id/action
        Matcher m = p.matcher(pathInfo);
        m.find();
        Long customerId;
        String action;
        try {
            customerId = Long.parseLong(m.group(1));
        } catch (Exception ex) {
            customerId = null;
        }
        try {
            action = m.group(3);
        } catch(IllegalStateException ex) {
            action = null;
        }
        ////////////////////////////////////////////////////////////////////////
        //CREATE
        if(pathInfo.equals("/new")) {
            // Add the customer to database
            Customer customer = new Customer(request.getParameter("firstName"),
                                request.getParameter("lastName"),
                                request.getParameter("address"),
                                request.getParameter("phoneNumber"));
            try {
                customerFacade.create(customer);
                request.setAttribute("customerName", customer.getName());
            } catch(Exception ex) {
                request.setAttribute("addCustomerFailureFlag", true);
            }
            fdPath = "/WEB-INF/view/customers/addCustomer.jsp";
        }
        ////////////////////////////////////////////////////////////////////////
        //READ
        else if (pathInfo.equals("")) {
            request.setAttribute("customers", customerFacade.findAll());
            fdPath = "/WEB-INF/view/customers/default.jsp";
        }
        ////////////////////////////////////////////////////////////////////////
        else if(pathInfo.equals("/search")) {
            try{
                request.setAttribute("results", customerFacade.queryByName(
                    request.getParameter("searchTerm")));}
            catch(Exception ex){
                request.setAttribute("searchCustomerFailureFlag", true);
            }

            fdPath = "/WEB-INF/view/customers/searchResults.jsp";
        }
        ////////////////////////////////////////////////////////////////////////
        else if (customerId != null && action == null) {
            //View customer with this id, if they exist.
            Customer customer = customerFacade.find(customerId);
            if(customer != null) {
                request.setAttribute("customer", customer);
                fdPath = "/WEB-INF/view/customers/editCustomer.jsp";
            }
            else{
                request.setAttribute("faultyId", customerId);
                fdPath = "/WEB-INF/view/customers/noSuchCustomer.jsp";
            }
        }
        ////////////////////////////////////////////////////////////////////////
        //UPDATE
        else if(customerId !=null && action.equals("edit")){
            Customer customer = customerFacade.find(customerId);
            if(customer != null){
                try{
                    // Edit Customer entity with updated data
                    customer.setFirstName(request.getParameter("firstName"));
                    customer.setLastName(request.getParameter("lastName"));
                    customer.setAddress(request.getParameter("address"));
                    customer.setPhoneNumber(request.getParameter("phoneNumber"));

                    // Merge new customer entity with existing record with productId
                    customerFacade.edit(customer);
                    request.setAttribute("customerName", customer.getName());
                    request.setAttribute("customer", customer);
                }
                catch (Exception ex) {
                    request.setAttribute("updateCustomerFailureFlag", true);
                }
                fdPath = "/WEB-INF/view/customers/editCustomer.jsp";
            }
            else{
                fdPath = "/WEB-INF/view/customers/noSuchCustomer.jsp";
            }

        }
        ////////////////////////////////////////////////////////////////////////
        //DELETE
        else if (customerId != null && action.equals("remove")) {
            Customer customer = customerFacade.find(customerId);
            if(customer != null){
                    try {
                        customerFacade.remove(customer);
                        request.setAttribute("deletedCustomerName", customer.getName());
                        fdPath = "/WEB-INF/view/customers/deleteCustomer.jsp";
                    }
                    catch(Exception ex) {
                    request.setAttribute("deleteProductFailureFlag", true);
                    }
            }
            else{
                    request.setAttribute("faultyId", customerId);
                    fdPath = "/WEB-INF/view/customers/noSuchCustomer.jsp";
            }
        }
        ////////////////////////////////////////////////////////////////////////
        // Forward dispatch
        if(fdPath == null)
            fdPath = "/WEB-INF/jspf/error/404.jsp";

        request.getRequestDispatcher(fdPath).forward(request, response);
    }

    /** 
     * Returns a short description of the servlet.
     * @return a String containing servlet description
     */
    @Override
    public String getServletInfo() {
        return "Servlet to handle all requests with URL /customers/*";
    }// </editor-fold>

}
